<template>
  <div class="tr-select-tree-box">
    <el-select
      v-model="selectName"
      :disabled="disabled"
      multiple
      clearable
      collapse-tags
      ref="select"
      @clear="clearHandle"
      @remove-tag="removeTagHandle"
    >
      <el-input
        class="input"
        placeholder="请输入查询关键字"
        prefix-icon="el-icon-search"
        v-model="treeFilter"
        clearable
      ></el-input>
      <el-option hidden :key="valueWord" value="" label=""> </el-option>
      <el-tree
        class="tree-select"
        show-checkbox
        :check-strictly="checkStrictly"
        :data="treeData"
        :props="defaultProps"
        :expand-on-click-node="false"
        :check-on-click-node="true"
        :default-checked-keys="defaultKeys"
        @check-change="handleCheckChange"
        ref="tree"
        :node-key="valueWord"
        :default-expand-all="defExpandAll"
        :filter-node-method="filterNode"
      >
        <span slot-scope="{ data }">
          <span>{{ data[showWord] }}</span>
        </span>
      </el-tree>
    </el-select>
  </div>
</template>

<script>
export default {
  name: "TrSelectMultipleTree",
  props: {
    defExpandAll: {
      type: Boolean,
      default: false,
    },
    value: {
      type: [Array],
      default: () => [],
    },
    disabled: {
      type: Boolean,
      default: false,
    },
    checkStrictly: {
      type: Boolean,
      default: false,
    },
    treeData: {
      type: Array,
      default: () => [],
    },
    showWord: {
      type: String,
      default: "title",
    },
    valueWord: {
      type: String,
      default: "value",
    },
    ftObj: {
      type: Object,
      default: () => {},
    },
    defaultProps: {
      type: Object,
      default: () => ({
        children: "children",
        label: "label",
      }),
    },
  },
  data: () => ({
    selectVal: [],
    selectName: [],
    treeFilter: "",
    defaultKeys: [],
  }),
  watch: {
    selectVal(newValue) {
      this.$emit("input", newValue);
      if (newValue.length > 0) this.$emit("selectBack", this.ftObj);
    },
    treeFilter(val) {
      this.$refs.tree.filter(val);
    },
  },
  methods: {
    setCheckedById(obj) {
      this.$refs.tree.setChecked(obj, false);
      if (obj.children && obj.children.length > 0) {
        obj.children.forEach((item) => {
          this.setCheckedById(item);
        });
      }
    },
    removeTagHandle(val) {
      const fItem = this.$findByProperty(this.treeData, this.showWord, val);
      this.setCheckedById(fItem);
      this.$nextTick(() => {
        this.getValueHanle();
      });
    },
    handleCheckChange() {
      this.getValueHanle();
    },
    getValueHanle() {
      let list = this.$refs.tree.getCheckedNodes();
      this.selectVal = list.map((item) => item[this.valueWord]);
      this.selectName = list.map((item) => item[this.showWord]);
    },
    clearHandle() {
      this.defaultKeys = [];
      this.selectVal = [];
      this.selectName = [];
      this.$refs.tree.setCheckedKeys([]);
    },
    filterNode(value, data) {
      if (!value) return true;
      let filterRes = data[this.showWord].indexOf(value) !== -1;
      return filterRes;
    },
    initHandle() {
      this.defaultKeys = this.value;
      if (!this.value.length) return;
      const valueList = [];
      const nameList = [];
      this.value.forEach((item) => {
        const fItem = this.$findByProperty(this.treeData, "id", item);
        nameList.push(fItem[this.showWord]);
        valueList.push(fItem[this.valueWord]);
      });
      this.$nextTick(() => {
        this.selectVal = valueList;
        this.selectName = nameList;
      });
    },
  },

  mounted() {
    this.initHandle();
  },
};
</script>
